<template>
  <div
    class="flex flex-col items-center justify-center min-h-screen bg-gradient-to-r from-pink-300 via-purple-300 to-indigo-400"
  >
    <h1 class="text-4xl font-bold mb-8 text-white shadow-text">记忆配对游戏</h1>
    <div class="grid grid-cols-4 gap-4 mb-8">
      <div
        v-for="card in cards"
        :key="card.id"
        class="w-20 h-20 flex items-center justify-center text-4xl cursor-pointer transition-all duration-300"
        :class="{
          'bg-white': card.isFlipped || card.isMatched,
          'bg-blue-500': !card.isFlipped && !card.isMatched,
          'opacity-50': card.isMatched,
        }"
        @click="handleCardClick(card.id)"
      >
        <transition name="flip">
          <span v-if="card.isFlipped || card.isMatched">{{ card.emoji }}</span>
        </transition>
      </div>
    </div>
    <p class="text-xl mb-4 text-white shadow-text">步数: {{ moves }}</p>
    <div v-if="isGameOver" class="text-center">
      <h2 class="text-2xl font-bold mb-4 text-white shadow-text">
        恭喜你赢了!
      </h2>
      <button
        @click="initializeGame"
        class="px-4 py-2 bg-white text-blue-500 rounded-md hover:bg-blue-100 transition-colors duration-300"
      >
        再玩一次
      </button>
    </div>
  </div>
</template>

<script setup>
import { ref, onMounted } from "vue";
import confetti from "canvas-confetti";

const emojis = ["🐶", "🐱", "🐭", "🐹", "🐰", "🦊", "🐻", "🐼"];

const cards = ref([]);
const flippedCards = ref([]);
const moves = ref(0);
const isGameOver = ref(false);

const initializeGame = () => {
  const shuffledEmojis = [...emojis, ...emojis].sort(() => Math.random() - 0.5);
  cards.value = shuffledEmojis.map((emoji, index) => ({
    id: index,
    emoji,
    isFlipped: false,
    isMatched: false,
  }));
  flippedCards.value = [];
  moves.value = 0;
  isGameOver.value = false;
};

const handleCardClick = (id) => {
  if (
    flippedCards.value.length === 2 ||
    cards.value[id].isFlipped ||
    cards.value[id].isMatched
  )
    return;

  cards.value[id].isFlipped = true;
  flippedCards.value.push(id);

  if (flippedCards.value.length === 2) {
    moves.value++;
    checkForMatch();
  }
};

const checkForMatch = () => {
  const [firstId, secondId] = flippedCards.value;
  if (cards.value[firstId].emoji === cards.value[secondId].emoji) {
    cards.value[firstId].isMatched = true;
    cards.value[secondId].isMatched = true;
    flippedCards.value = [];

    if (cards.value.every((card) => card.isMatched)) {
      isGameOver.value = true;
      confetti({
        particleCount: 100,
        spread: 70,
        origin: { y: 0.6 },
      });
    }
  } else {
    setTimeout(() => {
      cards.value[firstId].isFlipped = false;
      cards.value[secondId].isFlipped = false;
      flippedCards.value = [];
    }, 1000);
  }
};

onMounted(() => {
  initializeGame();
});
</script>

<style scoped>
.shadow-text {
  text-shadow: 2px 2px 4px rgba(0, 0, 0, 0.5);
}

.flip-enter-active,
.flip-leave-active {
  transition: all 0.3s ease;
}

.flip-enter-from,
.flip-leave-to {
  transform: rotateY(180deg);
  opacity: 0;
}
</style>
